package celiasoft.itasalib.query;

import java.util.List;

import org.w3c.dom.Document;

import android.graphics.Bitmap;
import android.util.Log;
import celiasoft.itasalib.filegatherer.IGatherer;
import celiasoft.itasalib.query.result.QueryResult;
import celiasoft.itasalib.query.result.QueryResultError;
import celiasoft.itasalib.query.resultparser.IQueryResultParser;
import celiasoft.itasalib.query.resultparser.QueryResultParserError;
import celiasoft.itasalib.structures.DataElement;

public abstract class Query {

	private final static String TAG = "itasalib.query";
	
	private final IGatherer _gatherer;
	private final String _apikey;
	private final QueryResultParserError _errParser;
	
	public Query(IGatherer gatherer, String apikey){
		this._apikey = apikey;
		this._gatherer = gatherer;
		this._errParser = new QueryResultParserError();
	}
	
	public QueryResult execute(){
        
		String queryUrl = this.getQueryUrl().replaceAll("&$", "");
		Log.d(TAG, "Actual query:" + queryUrl);
		
		if(queryUrl != null){
			Document doc = _gatherer.getDocument(queryUrl);
			
			return  buildResult(doc);
			
		}
		
		return null;
	}
	
	
	protected QueryResult buildResult(Document doc) {
		
		if(doc == null){
			return new QueryResult(new QueryResultError(400, "Generic Error"));
		}
		
		QueryResult qr = _errParser.parse(doc);
		if(qr != null){
			return qr;
		}
		
		ResultsMetaInfo meta = new ResultsMetaInfo();
		List<DataElement> res = getResultParser().parse(doc, meta);
		if(res != null){
			Log.d(TAG, "ok");
			return new QueryResult(res, meta);
		}
		
		Log.d(TAG, "null");
		return null;
			
	}
	

	public DataElement getFirstResult(){
		
		QueryResult qResult = this.execute();
		if(!qResult.isStatusOk()){
			return null;
		}
		
		List<DataElement> result = qResult.getDataResult(); 
		 
		if(result != null 
				&& result.size() > 0)
			return result.get(0);
		
		return null;
	}
	
	public Bitmap getImageResult(){
		return null;
	}
	
	protected String getAPIKey(){
		return this._apikey;
	}
	
	protected IGatherer getGatherer(){
		return _gatherer;
	}
		
	
	protected abstract String getQueryUrl();
	
	protected abstract IQueryResultParser getResultParser();

	/**
	 * @return the errParser
	 */
	public QueryResultParserError getErrParser() {
		return _errParser;
	}

	public void cacheResult(boolean cacheIt){
		this._gatherer.cacheResult(cacheIt);
	}
	
}
